/* ****************************************************************************
 *
 * Copyright (c) Microsoft Corporation. 
 *
 * This source code is subject to terms and conditions of the Microsoft Public License. A 
 * copy of the license can be found in the License.html file at the root of this distribution. If 
 * you cannot locate the  Microsoft Public License, please send an email to 
 * dlr@microsoft.com. By using this source code in any fashion, you are agreeing to be bound 
 * by the terms of the Microsoft Public License.
 *
 * You must not remove this notice, or any other, from this software.
 *
 * THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY
 * KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
 * PARTICULAR PURPOSE.
 * ***************************************************************************/




#if !defined(AFX_PGLPAVE_H__FE1AB0CC_4BE8_4138_A5DB_4F4EAAC1CCEA__INCLUDED_)
#define AFX_PGLPAVE_H__FE1AB0CC_4BE8_4138_A5DB_4F4EAAC1CCEA__INCLUDED_

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

#include <pgl/core/PGLLine.h>
#include <pgl/core/PGLCoord2D.h>
#include <pgl/core/PGLArea2D.h>

/*! \brief A rectangle region class

	\ingroup PGLRegionGroup

The rectangle region is characterized by
<ul>
	<li>inner border size,
	<li>outer border size,
	<li>outer border shadow.
</ul>
\image html pave.png "Pave description"
*/
class PGLCORE_EXT_CLASS CPGLPave : public CPGLLine
{
PGL_DECLARE_DYNCREATE(CPGLPave);
public:

//! Different types of border.
enum EPaveBorderType
{
	//! no border
	BorderNone=				0x0001,
	//! simple line
	BorderLine=				0x0002,
	//! full plain border
	BorderPlain=			0x0004,
	//! not implemeted
	BorderEmboss=			0x0008,
	//! not implemented
	BorderSunken=			0x0010,
	//! shadow located at lower left
	BorderLowerLeftShadow=	0x0020,
	//! shadow located at lower right
	BorderLowerRightShadow= 0x0040,
	//! shadow located at upper left
	BorderUpperLeftShadow=	0x0080,
	//! shadow located at upper right
	BorderUpperRightShadow= 0x0100
};

public:
	//! \name Constructors
	//@{
	//! Default
	CPGLPave(const CPGLColor& _FrontColor=CPGLColor(), const CPGLColor& _FillColor=CPGLColor(1,1,1,1),
		EPaveBorderType eBorderType = BorderNone);
	//! Copy constructor
	CPGLPave(const CPGLPave& p){*this=p;};
	//! Assignement constructor
	CPGLPave& operator = (const CPGLPave& p);
	virtual ~CPGLPave();
	//@}

	//! \name GUI
	//@{
	//! Adds the property page the property sheet
	virtual void AddPropertyPage(CPropertySheet* pPropSheet);
	//@}

	//! \name Area
	//@{
	//! returns Area object
	const CPGLArea2D& GetArea() const		{	return m_rArea;};
	//! returns Area object
	CPGLArea2D& GetArea()					{	return m_rArea;};
	//! Sets the are object
	void SetArea(const CPGLArea2D& _rArea)	{	m_rArea = _rArea;};
	//@}

	//!\name Border
	//@{
	//! Returns border type
	EPaveBorderType GetBorderType() const							{	return m_eBorderType;};
	//! Sets border type (see enum)
	void SetBorderType( EPaveBorderType e)							{	m_eBorderType = e;};
	//! Return outside border size in pixel	
	const CPGLRectD& GetBorderSize() const							{	return m_rBorderSize;};
	//! Set outside border size in pixel
	void SetBorderSize( const CPGLRectD& rBorderSize)				{	m_rBorderSize = rBorderSize;};
	//! Return inside border size in pixel	
	const CPGLRectD& GetInsideBorderSize() const					{	return m_rInsideBorderSize;};
	//! Set inside border size in pixel
	void SetInsideBorderSize( const CPGLRectD& rInsideBorderSize)	{	m_rInsideBorderSize = rInsideBorderSize;};
	//! Return the total (inside + outside) border size
	CPGLRectD GetTotalBorderSize() const;
	//@}

	//! \name Bounding box
	//@{
	//! Returns outside world bounding box (in world coordinate)
	CPGLRectD GetOutsideBBox() const	{	return m_rArea.GetBBox();};
	//! Returns inside world bounding box (in world coordinate)
	CPGLRectD GetInsideWorldBBox(const gfxinterface::CGfxInterface& gfx) const;
	//! Make the outside bbox grow so that it matches the inside bounding box size
	void GrowInsideBBAbsToOutsideNormBBox(gfxinterface::CGfxInterface& gfx, double dWidth, double dHeight);
	//@}

	//! \name Scripting methods
	//@{
	//! property enumeration
	enum EPaveProp
	{
		PavePropUnknow,
		//! border type
		PavePropBorderType
	};
	PGL_DECLARE_SCRIPTING(Pave);
	//@}

	//! \name Virtual plotting override
	//@{
	//! Main plot function
	void PlotGfx(gfxinterface::CGfxInterface& gfx);
	//@}

	//! \name Serialzation and debugging
	//@{
	//! Serialize functions
	void SerializeXML(CPGLArchive& ar);

	#ifdef _DEBUG
		//! MFC Dump
	    virtual void Dump( CDumpContext& dc ) const;
	    //! MFC AssertValid
	    virtual void AssertValid() const;   
	#endif
	//@}

private:
	//! \name Attributes
	//@{
	//! Bounding box
	CPGLArea2D m_rArea;
	//! Border Type
	EPaveBorderType m_eBorderType;
	//! Outside border size (pixels)
	CPGLRectD m_rBorderSize;
	//! Inside border size (pixels)
	CPGLRectD m_rInsideBorderSize;
	//! Polymorphic coordinate of Anchor
	CPGLCoord2D m_cAnchorPos;
	//@}
};

PGL_DECLARE_SMARTPTR( CPGLPave );

#endif // !defined(AFX_PGLPAVE_H__FE1AB0CC_4BE8_4138_A5DB_4F4EAAC1CCEA__INCLUDED_)
